package main

import "fmt"

/*
1、接口和继承的关系：
实现接口可以在不破坏继承的基础上，对结构体进行功能的扩展
2、区别
(1)接口和继承解决的问题不同
继承的价值主要在于：解决代码的复用性和可维护性
接口的价值主要在于：设计，设计好各种规范(方法)，让其它自定义类型去实现这些方法
(2)接口比继承更加灵活
继承是满足is - a的关系，而接口只需要满足like - a的关系
(3)接口在一定程度上实现代码解耦
*/
//Monkey结构体
type Monkey struct {
	Name string
}

//声明接口
type BirdAble interface {
	Flying()
}
type FishAble interface {
	Swimming()
}

func (this *Monkey) climbing() {
	fmt.Println(this.Name, "生来会爬树...")
}

//LittleMonkey结构体
type LittleMonkey struct {
	Monkey //继承
}

//让LittleMoneky实现接口
func (this *LittleMonkey) Flying() {
	fmt.Println(this.Name, "通过学习，会飞翔...")
}

func (this *LittleMonkey) Swimming() {
	fmt.Println(this.Name, "通过学习，会游泳...")
}

func main() {
	//创建一个LittleMonkey实例
	monkey := &LittleMonkey{
		Monkey{
			Name: "悟空",
		},
	}
	monkey.climbing()
	var BirdMonkey BirdAble = monkey
	BirdMonkey.Flying()
	var FishMonkey FishAble = monkey
	FishMonkey.Swimming()
	/*
		总结：
		(1)当A结构体继承了B结构体，那么A结构体就自动的继承了B结构体的字段和方法，并且可以直接使用
		(2)当A结构体需要扩展功能，同时不希望去破坏继承关系，则可以去实现某个接口即可，因此可以认为实现接口是对继承机制的补充
	*/
}
